package com.cmcc.groupcontacts.util;

import java.io.IOException;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.io.Writer;

import android.util.Log;

import com.cmcc.groupcontacts.common.Const;

/**
 * 异常捕获处理
 * 
 * @author 
 * 
 */
public abstract class ExceptionHandler {
	private static final String LOG_TAG = "ExceptionHandler";
	private static final String EXCEPTION_TYPE_DEFAULT = "[手动捕获]"; // 默认异常类型
	private static final String EXCEPTION_TYPE_ACCEPT = "[可容异常]"; // 可容异常类型

	/**
	 * 处理异常，将异常堆栈信息发送到友盟
	 * 
	 * @param e
	 */
	public static void handle(Throwable e) {
		handle(e, null);
	}

	/**
	 * 处理异常，将异常堆栈信息发送到友盟
	 * 
	 * @param e
	 * @param errorInfo
	 */
	public static void handle(Throwable e, String errorInfo) {
		handle(e, null, errorInfo);
	}

	/**
	 * 处理可容异常，将异常堆栈信息发送到友盟
	 * 
	 * @param e
	 */
	public static void handleAcceptable(Throwable e) {
		handle(e, EXCEPTION_TYPE_ACCEPT, null);
	}

	/**
	 * 处理可容异常，将异常堆栈信息发送到友盟
	 * 
	 * @param e
	 * @param errorInfo
	 */
	public static void handleAcceptable(Throwable e, String errorInfo) {
		handle(e, EXCEPTION_TYPE_ACCEPT, errorInfo);
	}

	/**
	 * 处理异常，将异常堆栈信息发送到友盟
	 * 
	 * @param e
	 * @param prefix
	 * @param errorInfo
	 */
	public static void handle(Throwable e, String prefix, String errorInfo) {
		if (Const.IS_DEBUG) { // 调试状态在控制台打印异常信息
			Log.e(LOG_TAG, "调试状态", e);
		} else { // 发布状态将异常发送到友盟
			// String traceInfo = getTraceInfo(e, prefix, errorInfo);
			// if (!ValidationUtil.isNullOrEmpty(traceInfo)) {
			// MobclickAgent.reportError(MainApp.getContext(), traceInfo);
			// }
		}
	}

	/**
	 * 获取异常堆栈信息
	 * 
	 * @param e
	 * @return 异常堆栈信息
	 */
	public static String getTraceInfo(Throwable e) {
		return getTraceInfo(e, null, null);
	}

	/**
	 * 获取异常堆栈信息
	 * 
	 * @param e
	 * @param errorInfo
	 * @return 异常堆栈信息
	 */
	public static String getTraceInfo(Throwable e, String errorInfo) {
		return getTraceInfo(e, null, errorInfo);
	}

	/**
	 * 获取异常堆栈信息
	 * 
	 * @param e
	 * @param prefix
	 * @param errorInfo
	 * @return 异常堆栈信息
	 */
	public static String getTraceInfo(Throwable e, String prefix, String errorInfo) {
		Writer infoWriter = null;
		PrintWriter printWriter = null;
		try {
			infoWriter = new StringWriter();
			printWriter = new PrintWriter(infoWriter);
			e.printStackTrace(printWriter);

			Throwable cause = e.getCause();
			while (cause != null) {
				cause.printStackTrace(printWriter);
				cause = cause.getCause();
			}

			if (ValidationUtil.isNullOrEmpty(prefix)) {
				prefix = EXCEPTION_TYPE_DEFAULT;
			}
			if (ValidationUtil.isNullOrEmpty(errorInfo)) {
				return prefix + infoWriter.toString();
			} else {
				return StringUtil.format("{0}{1}\n\t{2}", prefix, errorInfo, infoWriter.toString());
			}
		} catch (Exception e1) {
			return null;
		} finally {
			if (printWriter != null) {
				printWriter.close();
			}
			if (infoWriter != null) {
				try {
					infoWriter.close();
				} catch (IOException e2) {
				}
			}
		}
	}
}
